package com.microservice.salmon.oauth.client;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.oauth2.common.exceptions.UnapprovedClientAuthenticationException;
import org.springframework.security.web.authentication.AuthenticationFailureHandler;
import org.springframework.stereotype.Component;
import org.springframework.web.filter.OncePerRequestFilter;

import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * <p>
 * 校验是商家、后台管理 还是商城用户的登录
 * </p>
 *
 * @author 王洪庆 2019-01-10 23:04
 */
@Component("clientCheckFilter")
public class ClientCheckFilter extends OncePerRequestFilter {

    /**
     * 验证码校验失败处理器
     */
    @Autowired
    private AuthenticationFailureHandler authenticationFailureHandler;

    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain)
            throws ServletException, IOException {
        String header = request.getHeader("Authorization");
        if (header == null || !header.toLowerCase().startsWith("basic ")) {
            chain.doFilter(request, response);
            return;
        }
        String[] tokens;
        try {
            tokens = ClientProcessorHolder.extractAndDecodeHeader(header);
            assert tokens.length == 2;
        } catch (BadCredentialsException | UnapprovedClientAuthenticationException exception) {
            authenticationFailureHandler.onAuthenticationFailure(request, response, exception);
            return;
        }
        //记录客户端信息，从而可以通过不同的客户端（APP 微信、系统管理等等）, 转换为消息进行添加
        ClientProcessorHolder.addClientInfo(new ClientInfo(tokens[0]));
        chain.doFilter(request, response); // 继续后续的操作
        //当过滤器链返回的时候，删除记录的clientInfo
        ClientProcessorHolder.removeClientInfo();
    }

}
